package com.sheng.leetcode.year2025.month09.day24;

import org.junit.Test;

import java.util.HashMap;
import java.util.Map;

/**
 * @author by ls
 * @date 2025/9/26
 * <p>
 * 166. 分数到小数 <p>
 * <p>
 * 给定两个整数，分别表示分数的分子 numerator 和分母 denominator，以 字符串形式返回小数 。 <p>
 * 如果小数部分为循环小数，则将循环的部分括在括号内。 <p>
 * 如果存在多个答案，只需返回 任意一个 。 <p>
 * 对于所有给定的输入，保证 答案字符串的长度小于 10^4 。 <p>
 * <p>
 * 示例 1： <p>
 * 输入：numerator = 1, denominator = 2 <p>
 * 输出："0.5" <p>
 * <p>
 * 示例 2： <p>
 * 输入：numerator = 2, denominator = 1 <p>
 * 输出："2" <p>
 * <p>
 * 示例 3： <p>
 * 输入：numerator = 4, denominator = 333 <p>
 * 输出："0.(012)" <p>
 * <p>
 * 提示： <p>
 * -2^31 <= numerator, denominator <= 2^31 - 1 <p>
 * denominator != 0 <p>
 */
public class LeetCode0166 {

    @Test
    public void test() {
//        int numerator = 1, denominator = 2;
//        int numerator = 2, denominator = 1;
        int numerator = 4, denominator = 333;
        System.out.println(new Solution().fractionToDecimal(numerator, denominator));
    }
}

class Solution {
    public String fractionToDecimal(int numerator, int denominator) {
        if (numerator == 0) {
            return "0";
        }
        StringBuilder sb = new StringBuilder();
        // 判断符号
        if ((numerator < 0) ^ (denominator < 0)) sb.append("-");

        // 转成 long 避免溢出
        long num = Math.abs((long) numerator);
        long den = Math.abs((long) denominator);
        // 整数部分
        sb.append(num / den);
        // 是否存在剩余
        long remainder = num % den;
        if (remainder == 0) {
            return sb.toString();
        }

        sb.append(".");
        // 记录余数出现的位置
        Map<Long, Integer> map = new HashMap<>();

        while (remainder != 0) {
            if (map.containsKey(remainder)) {
                int index = map.get(remainder);
                sb.insert(index, "(");
                sb.append(")");
                break;
            }
            map.put(remainder, sb.length());
            remainder *= 10;
            sb.append(remainder / den);
            remainder %= den;
        }

        return sb.toString();
    }
}
